home *** CD-ROM | disk | FTP | other *** search
/ Power Programmierung 2 / Power-Programmierung CD 2 (Tewi)(1994).iso / gnu / gnulib / sipp / libsipp / basic_sh.c next >
Encoding:
C/C++ Source or Header  |  1992-05-03  |  3.1 KB  |  102 lines

  1. /**
  2.  ** sipp - SImple Polygon Processor
  3.  **
  4.  **  A general 3d graphic package
  5.  **
  6.  **  Copyright Equivalent Software HB  1992
  7.  **
  8.  ** This program is free software; you can redistribute it and/or modify
  9.  ** it under the terms of the GNU General Public License as published by
  10.  ** the Free Software Foundation; either version 1, or any later version.
  11.  ** This program is distributed in the hope that it will be useful,
  12.  ** but WITHOUT ANY WARRANTY; without even the implied warranty of
  13.  ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  14.  ** GNU General Public License for more details.
  15.  ** You can receive a copy of the GNU General Public License from the
  16.  ** Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  17.  **/
  18.  
  19. /**
  20.  ** basic_shader.c - Basic shading model, somewhat modified and 
  21.  **                  simplified version of Blinn's
  22.  **/
  23.  
  24. #include <math.h>
  25.  
  26. #include <sipp.h>
  27. #include <geometric.h>
  28.  
  29. void
  30. basic_shader(pos, normal, texture, view_vec, lights, sd, color, opacity)
  31.     Vector      *pos;
  32.     Vector      *normal;
  33.     Vector      *texture;
  34.     Vector      *view_vec;
  35.     Lightsource *lights;
  36.     Surf_desc   *sd;
  37.     Color       *color;
  38.     Color       *opacity;
  39. {
  40.     Vector       unit_norm;
  41.     Vector       light_dir;
  42.     Vector       specular;
  43.     Color        diffsum;
  44.     Color        specsum;
  45.     double       coss, cosi;
  46.     double       c3two;
  47.     double       shadow_fact;
  48.     double       tmp;
  49.     Lightsource *lp;
  50.  
  51.     VecCopy(unit_norm, *normal);
  52.     vecnorm(&unit_norm);
  53.     diffsum.red = diffsum.grn = diffsum.blu = 0.0;
  54.     specsum.red = specsum.grn = specsum.blu = 0.0;
  55.     c3two = sd->c3 * sd->c3;
  56.  
  57.     for (lp = lights; lp != (Lightsource *)0; lp = lp->next) {
  58.  
  59.         shadow_fact = light_eval(lp, pos, &light_dir);
  60.  
  61.         if (shadow_fact > 0.0001) {
  62.             cosi = VecDot(light_dir, unit_norm);
  63.             if (cosi > 0) {
  64.                 tmp = cosi * shadow_fact;
  65.                 diffsum.red += lp->color.red * tmp;
  66.                 diffsum.grn += lp->color.grn * tmp;
  67.                 diffsum.blu += lp->color.blu * tmp;
  68.             }
  69.         
  70.             cosi *= 2.0;
  71.             VecComb(specular, -1.0, light_dir, cosi, unit_norm);
  72.             coss = VecDot(specular, *view_vec);
  73.             if (coss > 0) {
  74.                 tmp = (shadow_fact * c3two * coss 
  75.                        / (coss * coss * (c3two -1) + 1));
  76.                 specsum.red += lp->color.red * tmp;
  77.                 specsum.grn += lp->color.grn * tmp;
  78.                 specsum.blu += lp->color.blu * tmp;
  79.             }
  80.         }
  81.     }
  82.  
  83.     color->red = (sd->color.red * (sd->ambient + diffsum.red) 
  84.                   + sd->specular * specsum.red); 
  85.     if (color->red > 1.0) color->red = 1.0;
  86.  
  87.     color->grn = (sd->color.grn * (sd->ambient + diffsum.grn) 
  88.                   + sd->specular * specsum.grn); 
  89.     if (color->grn > 1.0) color->grn = 1.0;
  90.  
  91.     color->blu = (sd->color.blu * (sd->ambient + diffsum.blu) 
  92.                   + sd->specular * specsum.blu);
  93.     if (color->blu > 1.0) color->blu = 1.0;
  94.  
  95.     opacity->red = sd->opacity.red;
  96.     opacity->grn = sd->opacity.grn;
  97.     opacity->blu = sd->opacity.blu;
  98. }
  99.  
  100.  
  101.  
  102.